/*
 * parser.cpp
 *
 *  Created on: 27-Apr-2009
 *      Author: catchthealien
 */

#include <cssysdef.h>

#include <string>
#include <iostream>
#include <sstream>
#include <stdexcept>
#include <list>

#include <sys/types.h>
#include <sys/stat.h>
//#include <unistd.h>
#include <errno.h>

#include "parser.h"

using namespace std;

namespace cta {

/**
 *  Constructor initializes xerces-C libraries.
 *  The XML tags and attributes which we seek are defined.
 *  The xerces-C DOM parser infrastructure is initialized.
 */

parser::parser() {
	// TODO Auto-generated constructor stub

	}

	/**
	 *  Class destructor frees memory used to hold the XML tag and
	 *  attribute definitions. It als terminates use of the xerces-C
	 *  framework.
	 */

parser::~parser() {
	// TODO Auto-generated destructor stub

}

int parser::getInteger(char* configFile, char* p_tag, char* p_attr)
{
	std::string strConfigFile = configFile;
	std::string strP_tag = p_tag;
	std::string strP_attr = p_attr;
	return getInteger(strConfigFile, strP_tag, strP_attr);
}

int parser::getInteger(std::string& configFile, char* p_tag, char* p_attr)
{
	std::string strP_tag = p_tag;
	std::string strP_attr = p_attr;
	return getInteger(configFile, strP_tag, strP_attr);
}

int parser::getInteger(std::string& configFile, std::string& p_tag, std::string& p_attr)
{
	std::stringstream return_(getString(configFile,p_tag,p_attr));
	int returni_ = (-1);
	return_ >> returni_;
	return returni_;
}

int parser::getIntegerFromString(std::string& configFile, char* p_tag, char* p_attr)
{
	std::string strP_tag = p_tag;
	std::string strP_attr = p_attr;
	return getIntegerFromString(configFile, strP_tag, strP_attr);
}

int parser::getIntegerFromString(std::string& configFile, std::string& p_tag, std::string& p_attr)
{
	std::stringstream return_(getStringFromString(configFile,p_tag,p_attr));
	int returni_ = (-1);
	return_ >> returni_;
	return returni_;
}

float parser::getFloatFromString(std::string& configFile, char* p_tag, char* p_attr)
{
	std::string strP_tag = p_tag;
	std::string strP_attr = p_attr;
	return getFloatFromString(configFile, strP_tag, strP_attr);
}

float parser::getFloatFromString(std::string& configFile, std::string& p_tag, std::string& p_attr)
{
	std::stringstream return_(getStringFromString(configFile,p_tag,p_attr));
	float returnf_ = (-1);
	return_ >> returnf_;
	return returnf_;
}

std::string parser::getString(std::string& configFile, char* p_tag, char* p_attr)
{
	std::string p_tag_ = p_tag;
	std::string p_attr_ = p_attr;
	return getString(configFile, p_tag_, p_attr_);
}

std::string parser::getString(std::string& configFile, std::string& p_tag, std::string& p_attr)
{
    QFile file(configFile.c_str());
    QDomDocument XmlDoc;
    XmlDoc.setContent(&file);

    QDomElement ElementRoot = XmlDoc.documentElement();
    QDomNodeList Children = ElementRoot.childNodes();
    int NodeCount = Children.length();
    for (int xx = 0; xx<NodeCount; ++xx)
    {
        QDomNode CurrentNode = Children.item(xx);
        if( CurrentNode.nodeType() &&
            CurrentNode.nodeType() == QDomNode::ElementNode)
        {
            QDomElement CurrentElement
                    = CurrentNode.toElement();
            if( CurrentElement.tagName() == p_tag.c_str())
            {
                std::string return_ = CurrentElement.attribute(p_attr.c_str()).toStdString();
                return return_;
            }
        }
    }
    return "";
}

std::string parser::getStringFromString(std::string& p_String, char* p_tag, char* p_attr)
{
	std::string p_tag_ = p_tag;
	std::string p_attr_ = p_attr;
	return getStringFromString(p_String, p_tag_, p_attr_);
}

std::string parser::getStringFromString(std::string& p_String, std::string& p_tag, std::string& p_attr)
{
    QString str = p_String.c_str();
    QDomDocument XmlDoc;
    XmlDoc.setContent(str);

    QDomElement ElementRoot = XmlDoc.documentElement();
    QDomNodeList Children = ElementRoot.childNodes();
    int NodeCount = Children.length();
    for (int xx = 0; xx<NodeCount; ++xx)
    {
        QDomNode CurrentNode = Children.item(xx);
        if( CurrentNode.nodeType() &&
            CurrentNode.nodeType() == QDomNode::ElementNode)
        {
            QDomElement CurrentElement
                    = CurrentNode.toElement();
            if( CurrentElement.tagName() == p_tag.c_str())
            {
                std::string return_ = CurrentElement.attribute(p_attr.c_str()).toStdString();
                return return_;
            }
        }
    }
    return "";
}
/*
std::string parser::getStringFromString(std::string& p_String, std::string& p_tag, std::string& p_attr)
{

        StringParser_ = new XercesDOMParser;
                   StringParser_->setValidationScheme( XercesDOMParser::Val_Never );
                   StringParser_->setDoNamespaces( false );
                   StringParser_->setDoSchema( false );
                   StringParser_->setLoadExternalDTD( false );

                   try
                      {
                           StringParser_ = new XercesDOMParser();
                           InputSource* inSource = new MemBufInputSource((const unsigned char*)p_String.c_str(), p_String.length(), "1", false);
                           StringParser_->parse(*inSource);
                           delete inSource;
                        DOMDocument* xmlDoc = StringParser_->getDocument();

                         // Get the top-level element: NAme is "root". No attributes for "root"

                         DOMElement* elementRoot = xmlDoc->getDocumentElement();
                         if( !elementRoot ) throw(std::runtime_error( "empty XML document" ));

                         // Parse XML file for tags of interest: "ApplicationSettings"
                         // Look one level nested within "root". (child of root)

                         DOMNodeList*      children = elementRoot->getChildNodes();
                         const  XMLSize_t nodeCount = children->getLength();

                         // For all nodes, children of "root" in the XML tree.

                         for( XMLSize_t xx = 0; xx < nodeCount; ++xx )
                         {
                            DOMNode* currentNode = children->item(xx);
                            if( currentNode->getNodeType() &&  // true is not NULL
                                currentNode->getNodeType() == DOMNode::ELEMENT_NODE ) // is element
                            {
                               // Found node which is an Element. Re-cast node as element
                               DOMElement* currentElement
                                           = dynamic_cast< xercesc::DOMElement* >( currentNode );
                               if( XMLString::equals(currentElement->getTagName(), XMLString::transcode(p_tag.c_str())))
                               {
                                  // Already tested node as type element and of name "ApplicationSettings".
                                  // Read attributes of element "ApplicationSettings".
                                  std::string return_ = xercesc::XMLString::transcode(
                                                                                          currentElement->getAttribute(XMLString::transcode(p_attr.c_str())));
                                  return return_;
                               }
                            }
                         }
                      }
                      catch( xercesc::XMLException& e )
                      {
                         char* message = xercesc::XMLString::transcode( e.getMessage() );
                         ostringstream errBuf;
                         errBuf << "Error parsing file: " << message << flush;
                         XMLString::release( &message );
                      }

                      return "";

}*/

}
